package com.kk.xhr.model.service.impl;

import com.kk.xhr.common.pojo.BinaryEnum;
import com.kk.xhr.model.assembler.SalaryStructKit;
import com.kk.xhr.model.dao.SalaryDynamicSqlSupport;
import com.kk.xhr.model.dao.SalaryMapper;
import com.kk.xhr.model.dto.PageDto;
import com.kk.xhr.model.dto.SalaryDTO;
import com.kk.xhr.model.entity.Salary;
import com.kk.xhr.model.service.ISalaryService;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Repository;

import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;

import static org.mybatis.dynamic.sql.SqlBuilder.isEqualTo;
import static org.mybatis.dynamic.sql.SqlBuilder.isEqualToWhenPresent;

/**
 * 薪资服务接口实现
 *
 * @author kkmystery
 * @version 1.0 2021/3/6
 * @since 1.0.0
 */
@Repository
@RequiredArgsConstructor
public class SalaryServiceImpl implements ISalaryService {
    private final SalaryMapper salaryMapper;
    private final SalaryStructKit instance = SalaryStructKit.INSTANCE;

    /**
     * {@inheritDoc}
     */
    @Override
    public Optional<SalaryDTO> queryById(Long id) {
        return salaryMapper.selectOne(dsl -> dsl
            .where(SalaryDynamicSqlSupport.id, isEqualTo(id))
            .and(SalaryDynamicSqlSupport.status, isEqualTo(BinaryEnum.TRUE.getValue())))
            .map(instance::toDto);
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public PageDto<SalaryDTO> queryPage(Long userId, Integer limit, Integer offset) {
        long count = salaryMapper.count(dsl -> dsl
            .where(SalaryDynamicSqlSupport.userId, isEqualToWhenPresent(userId))
            .and(SalaryDynamicSqlSupport.status, isEqualTo(BinaryEnum.TRUE.getValue())));
        if (0 == count) {
            return PageDto.empty();
        }
        return new PageDto<>(count, salaryMapper.select(dsl -> dsl
            .where(SalaryDynamicSqlSupport.userId, isEqualToWhenPresent(userId))
            .and(SalaryDynamicSqlSupport.status, isEqualTo(BinaryEnum.TRUE.getValue()))
            .orderBy(SalaryDynamicSqlSupport.id.descending())
            .limit(limit)
            .offset(offset))
            .stream()
            .map(instance::toDto)
            .collect(Collectors.toList()));
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public Optional<SalaryDTO> queryByUserId(Long userId) {
        return salaryMapper.selectOne(dsl -> dsl
            .where(SalaryDynamicSqlSupport.userId, isEqualTo(userId))
            .and(SalaryDynamicSqlSupport.status, isEqualTo(BinaryEnum.TRUE.getValue()))
            .orderBy(SalaryDynamicSqlSupport.id.descending())
            .limit(1))
            .map(instance::toDto);
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public List<SalaryDTO> queryLog(Long userId) {
        return salaryMapper.select(dsl -> dsl
            .where(SalaryDynamicSqlSupport.userId, isEqualTo(userId))
            .and(SalaryDynamicSqlSupport.status, isEqualTo(BinaryEnum.FALSE.getValue()))
            .orderBy(SalaryDynamicSqlSupport.id.descending()))
            .stream()
            .map(instance::toDto)
            .collect(Collectors.toList());
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public boolean add(SalaryDTO dto) {
        return 1 == salaryMapper.insertSelective(instance.toEntity(dto));
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public boolean modify(SalaryDTO dto) {
        if (null == dto.getId()) {
            return false;
        }
        return 1 == salaryMapper.updateByPrimaryKeySelective(instance.toEntity(dto));
    }

    /**
     * {@inheritDoc}
     */
    @Override
    public boolean modifyStatus(Long id, BinaryEnum status) {
        if (null == status) {
            return false;
        }
        return 1 == salaryMapper.updateByPrimaryKeySelective(new Salary().withId(id).withStatus(status.getValue()));
    }
}
